;(function(win, debug) {
    win.MyPromise = MyPromise;

    function MyPromise(func) {
        if (typeof func !== 'function') {
            throw new Error('new MyPromise: arg is not a function');
        }

        var FINISH = 'MY_PROMISE_FINISH';

        var onFulfilled;
        var onRejected;
        var self = this;

        function resolve(future) {
            // 更新状态
            self._PromiseValue = future;
            self._PromiseStatus = 'resolved';

            if (typeof onFulfilled === 'function') {
                // 展开promise
                if (future instanceof MyPromise) {
                    // 把内层结果传递给外层
                    future.then(function() {
                        resolve(future._PromiseValue);
                    }, function(error) {
                        if (future._PromiseStatus === 'rejected') {
                            reject(future._PromiseValue);
                        }
                        else {
                            resolve(future._PromiseValue);
                        }
                    });
                }
                else {
                    // 直接传递给已添加的handler
                    self._PromiseValue = onFulfilled(future);
                }
            }

            throw new Error(FINISH);  // 跳出
        }
        function reject(error) {
            // 更新状态
            self._PromiseValue = error;
            self._PromiseStatus = 'rejected';

            if (typeof onRejected === 'function') {
                // 直接传递给已添加的handler
                self._PromiseValue = onRejected(error);
                // onRejected之后，状态为resolved
                self._PromiseStatus = 'resolved';
            }
            else {
                // 延迟50ms再检查报错（等待紧接着的then | catch）
                nextTick(function() {
                    if (typeof onRejected === 'function') {
                        // then已经处理过了，不报错
                        return;
                    }

                    // 报错
                    if (error instanceof Error) {
                        throw error;
                    }
                    else {
                        throw new Error('reject in MyPromise: ' + error);
                    }
                });
            }

            throw new Error(FINISH);  // 跳出
        }

        // 立即执行构造器传入的函数
        try {
            func(resolve, reject);
        } catch(err) {
            if (err instanceof Error && err.message === FINISH) {
                // do nothing
            }
            else {
                throw err;
            }
        }


        //------实例属性
        //---内部属性
        this._PromiseStatus = this._PromiseStatus || 'pending';

        //---公开属性
        // then 添加handler
        this.then = function(_onFulfilled, _onRejected) {
            if (typeof _onFulfilled === 'function') {
debug('add onFulfilled handler');
                onFulfilled = _onFulfilled;

                // 立即执行onFulfilled
                if (self._PromiseStatus === 'resolved') {
debug('onFulfilled now');
                    try {
                        resolve(self._PromiseValue);
                    } catch(err) {
                        if (err instanceof Error && err.message === FINISH) {
                            // do nothing
                        }
                        else {
                            throw err;
                        }
                    }
                }
            }
            if (typeof _onRejected === 'function') {
debug('add onRejected handler');
                onRejected = _onRejected;

                if (self._PromiseStatus === 'rejected') {
debug('onRejected now');
                    self._PromiseStatus = 'resolved';
                    try {
                        reject(self._PromiseValue);
                    } catch(err) {
                        if (err instanceof Error && err.message === FINISH) {
                            // do nothing
                        }
                        else {
                            throw err;
                        }
                    }
                }
            }

            // 支持链式调用
            return self;
        };
        // catch 添加否定handler
        this['catch'] = function(_onRejected) {
            if (typeof _onRejected === 'function') {
debug('add onRejected handler');
                onRejected = _onRejected;

                if (self._PromiseStatus === 'rejected') {
debug('onRejected now');
                    self._PromiseValue = onRejected(this._PromiseValue);
                    self._PromiseStatus = 'resolved';
                }
            }

            return self;
        };
    }
    //------静态属性
    //resolve 返回promise对象
    MyPromise.resolve = function(value) {
        var p;

        // promise不变
        if (value instanceof MyPromise) {
            p = value;
        }
        // 包装!promise
        else {
            p = new MyPromise(emptyF);

            // thenable
            if (typeof value === 'object' && typeof value.then === 'function') {
                // 把obj.then包起来
                var resolved = false;

                p.then = function(onFulfilled, onRejected) {
                    value.then(function(future) {
                        if (!resolved) {
                            nextTick(function() {
                                onFulfilled(future);
                            });
                            // 禁止触发onRejected
                            resolved = true;
                        }
                    }, function(error) {
                        if (!resolved) {
                            onRejected(error);
                            // 禁止触发onFulfilled
                            resolved = true;
                        }
                    });
                }
            }
            // !thenable
            else {
                p._PromiseValue = value;
                p._PromiseStatus = 'resolved';
            }
        }

        return p;
    };
    MyPromise.reject = function(reason) {
        var p = new MyPromise(emptyF);

        p._PromiseValue = reason;
        p._PromiseStatus = 'rejected';

        return p;
    };
    MyPromise.all = function(arr) {
        var p = new MyPromise(emptyF);
        var breakout = false;
        var futures = [];

        for (var i = 0; i < arr.length; i++) {
            if (arr[i] instanceof MyPromise) {
                arr[i].then(function(future) {
                    futures.push(future);
                }, function(error) {
                    if (!breakout) {
                        breakout = true;
                        p._PromiseStatus = 'rejected';
                        p._PromiseValue = error;
                    }
                });
                if (breakout) {
                // 吃掉集合中还没有.then()的否定promise
                arr[i]['catch'](emptyF);
            }
            }
            else {
                // !promise直接放进futures结果集
                futures.push(arr[i]);
            }
        }

        // 全肯定
        if (!breakout) {
            p._PromiseStatus = 'resolved';
            p._PromiseValue = futures;
        }

        return p;
    };
    MyPromise.race = function(arr) {
        var p = new MyPromise(emptyF);
        var breakout = false;

        for (var i = 0; i < arr.length; i++) {
            if (arr[i] instanceof MyPromise) {
                arr[i].then(function(future) {
                    if (!breakout) {
                        breakout = true;
                        p._PromiseStatus = 'resolved';
                        p._PromiseValue = future;
                    }
                }, function(error) {
                    if (!breakout) {
                        breakout = true;
                        p._PromiseStatus = 'rejected';
                        p._PromiseValue = error;
                    }
                });
                if (breakout) {
                    // 吃掉集合中还没有.then()的否定promise
                    arr[i]['catch'](emptyF);
                }
            }
            else {
                // !promise直接resolved
                if (!breakout) {
                    breakout = true;
                    p._PromiseStatus = 'resolved';
                    p._PromiseValue = arr[i];
                }
            }
        }

        return p;
    };

    //------工具方法
    function emptyF() {}
    function nextTick(fn) {
        setTimeout(fn, 0);
    }
})(window, function(arg) {
    // console.log(arg);
});